package com.zh.freechat.domain.user.repository;

import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.zh.freechat.domain.user.entity.UserContacts;
import com.zh.freechat.domain.user.entity.UserRelId;
import com.zh.freechat.domain.user.entity.UserRelationBlack;
import com.zh.freechat.domain.user.entity.UserRelationFriend;
import com.zh.freechat.domain.user.repository.real.UserRelationBlackMapper;
import com.zh.freechat.domain.user.repository.real.UserRelationFriendMapper;
import com.zh.mycommon.value.Tuple2;
import lombok.AllArgsConstructor;
import lombok.extern.slf4j.Slf4j;
import org.springframework.stereotype.Repository;
import org.springframework.transaction.annotation.Transactional;

import java.util.List;
import java.util.Map;
import java.util.Objects;
import java.util.stream.Collectors;


/**
 * @author ZH
 * @date 18:10 2021/7/31
 */
@Slf4j
@AllArgsConstructor
@Repository
public class UserContactRepository {
    private final UserRelationFriendMapper friendMapper;
    private final UserRelationBlackMapper blackMapper;

    @Transactional
    public void bothAddContact(String user1, String user2) {
        var relation = new UserRelationFriend(user1, user2);
        try {
            friendMapper.insert(relation);
        } catch (Exception ex) {
            log.error("保存好友关系[{},{}]失败：{}", relation.getUser1(), relation.getUser2(), ex.getMessage());
        }
    }

    @Transactional
    public void bothRemoveContact(String userId, String friendId) {
        var u1 = userId;
        var u2 = friendId;
        if (u1.compareTo(u2)> 0) {
            var t = u1;
            u1 = u2;
            u2 = t;
        }
        friendMapper.removeByUserId(userId, u1, u2);
        friendMapper.removeByUserId(friendId, u1, u2);
    }

    public void addBlack(UserRelationBlack black) {
        blackMapper.insert(black);
    }

    public void removeBlack(UserRelationBlack black) {
        var query = new QueryWrapper<UserRelationBlack>()
                .eq("user_id", black.getUserId()).eq("black_id", black.getBlackId());
        blackMapper.delete(query);
    }

    public UserContacts findContacts(String userId) {
        // SELECT * FROM ch_user_friend WHERE user1=userId or user2=userId
        var query1 = new QueryWrapper<UserRelationFriend>()
                .eq("user1", userId).or().eq("user2", userId);
        List<UserRelationFriend> friends = friendMapper.selectList(query1);

        // SELECT * FROM ch_user_black WHERE user_id=userId
        var query2 = new QueryWrapper<UserRelationBlack>()
                .eq("user_id", userId);
        List<UserRelationBlack> blacklist = blackMapper.selectList(query2);

        return new UserContacts(userId, friends, blacklist);
    }

    /**
     * 判断两个用户是不是好友关系
     *
     * @param user1Id 用户1
     * @param user2Id 用户2
     * @return boolean
     */
    public boolean isFriendRelation(String user1Id, String user2Id) {
        var u1 = user1Id;
        var u2 = user2Id;
        if (u1.compareTo(u2)> 0) {
            var t = u1;
            u1 = u2;
            u2 = t;
        }
        return friendMapper.existsFriendRelation(u1, u2) > 0;
    }

    /**
     * 用户是不是在此用户黑名单中
     * 即inquirerUser是不是在centralUser的黑名单上
     *
     * @param queryUserId 要查询的userId
     * @param centralUser 这个user的黑名单list
     * @return boolean
     */
    public boolean isBlacklist(String queryUserId, String centralUser) {
        var query = new QueryWrapper<UserRelationBlack>().eq("user_id", centralUser).eq("black_id", queryUserId);
        return blackMapper.selectCount(query) > 0;
    }

    /**
     * 获取users和当前user的relId
     *
     * @param userIds
     * @param currentUserId 当前用户userId
     */
    public Map<String, Long> getRelIdByUserIds(List<String> userIds, String currentUserId) {

        List<UserRelId> friendRelation = friendMapper.findRelIdByBothUserId(userIds, currentUserId);
        if (friendRelation.isEmpty()) {
            return Map.of();
        }
        return friendRelation
                .stream().collect(Collectors.toMap(e -> {
                    return Objects.equals(currentUserId, e.getUser1()) ? e.getUser2() : e.getUser1();
                }, a -> a.getId()));
    }
}






